#include <bits/stdc++.h>

using namespace std;

typedef long long ll;

#define in read()

int read(){
	int x = 0,sgn = 1;char ch = getchar();
	for(;!isdigit(ch);ch = getchar()) if(ch == '-') sgn = -1;
	for(;isdigit(ch);ch = getchar()) x = (x<<1)+(x<<3)+(ch^48);
	return x*sgn;
}

const int MAXN = 1e5+10;

int n,m,stk[MAXN],top;

struct node{
	int fa,val,ch[2],sum,lz;
}t[MAXN];

bool isroot(int x){return t[t[x].fa].ch[0] != x && t[t[x].fa].ch[1] != x;}

void pushup(int x){t[x].sum = t[t[x].ch[0]].sum ^ t[t[x].ch[1]].sum ^ t[x].val;}

void Rotate(int x){
	int y = t[x].fa,z = t[y].fa,k = t[y].ch[1] == x;
	if(!isroot(y)) t[z].ch[t[z].ch[1] == y] = x; t[x].fa = z;
	if(t[x].ch[k^1]) t[t[x].ch[k^1]].fa = y; t[y].ch[k] = t[x].ch[k^1];
	t[x].ch[k^1] = y; t[y].fa = x; pushup(y); pushup(x);
}

void pushdown(int x){
	if(!t[x].lz) return; t[t[x].ch[0]].lz ^= 1; t[t[x].ch[1]].lz ^= 1;t[x].lz = 0; swap(t[x].ch[0],t[x].ch[1]);
}

void Splay(int x){
	top = 0;stk[++top] = x;
	for(int i = x;!isroot(i);i = t[i].fa) stk[++top] = t[i].fa; while(top) pushdown(stk[top--]);
	while(!isroot(x)){
		int y = t[x].fa,z = t[y].fa;
		if(!isroot(y)) (t[z].ch[1] == y) ^ (t[y].ch[1] == x) ? Rotate(x) : Rotate(y);
		Rotate(x);
	}
}

void access(int x){
	for(int y = 0;x;y = x,x = t[x].fa) { Splay(x); t[x].ch[1] = y;pushup(x);}
}

void makeroot(int x){
	access(x); Splay(x); t[x].lz ^= 1;
}

int findroot(int x){
	access(x); Splay(x); while(t[x].ch[0]) pushdown(x),x = t[x].ch[0]; Splay(x); return x;
}

void Split(int x,int y){
	makeroot(x); access(y); Splay(y);
}

void link(int x,int y){
	makeroot(x); if(findroot(y) != x) t[x].fa = y;
}

void cut(int x,int y){
	makeroot(x); if(findroot(y) == x && t[y].fa == x && !t[y].ch[0]) t[x].ch[1] = t[y].fa = 0,pushup(x);
}

int main (){
	n = in,m = in;for(int i = 1;i <= n;i++) t[i].val = in;
	while(m--){
		int op = in,x = in,y = in;
		if(op == 0) {Split(x,y); printf("%d\n",t[y].sum);}
		else if(op == 1) link(x,y);
		else if(op == 2) cut(x,y);
		else makeroot(x),t[x].val = y,pushup(x);
	}
	return 0;
}
